package user;

import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;

import server.Connector;
import util.Message;
import util.Status;
import businessLogicService.UserBLService;
import dataPO.UserPO;

public abstract class User implements UserBLService {

    public static final int ADMIN = 0;
    public static final int SUB_ADMIN = 1;
    public static final int TEACHER = 2;
    public static final int STUDENT = 3;

    protected final String ID;
    protected String password;
    protected UserPO accountInfo;
    protected final int authorityLevel;

    private static final String[] USERS = { "user.Administrator", "user.SubAdministrator", "user.Teacher", "user.Student" };

    public User(int authorityLevel, String ID, String password) {
        this.authorityLevel = authorityLevel;
        this.ID = ID;
        this.password = password;
        this.accountInfo = (UserPO) Connector.getAccountInfo(ID).getItem();
    }

    public String getDepartment() {
        return accountInfo.getDepartment();
    }

    @Override
    public Message modifyPassword(String newPassword) {
        this.password = newPassword;
        this.accountInfo.setPassword(newPassword);
        return Connector.update(this.accountInfo);
    }

    @Override
    public Message getCourses(String department, String grade, String type, String teacher) {
        return Connector.getCoursesBy(department, grade, type, teacher);
    }

    @Override
    public Message showMyAccountInfo() {
        return Connector.getAccountInfo(this.ID);
    }

    @Override
    public Message showTeachFrameInfo() {
        return Connector.getTeachFrameItems();
    }

    @Override
    public Message showTeachPlan(String department) {
        return Connector.getTeachPlanItems(department);
    }

    public String getUserType() {
        if (accountInfo == null) {
            return null;
        }
        return this.accountInfo.getUserType();
    }

    public String getName() {
        if (accountInfo == null) {
            return null;
        }
        return this.accountInfo.getName();
    }

    public String getPassword() {
        return this.password;
    }

    public static Message login(String userID, String password) {
        Message info = Connector.getAccountInfo(userID);
        
        try {
            UserPO item = (UserPO) info.getItem();
            if (password.equals(item.getPassword())) {

                int index = Integer.parseInt( item.getAuthorityLevel() );

                Class<?> c = Class.forName(USERS[index]);
                Constructor<?> cons = c.getConstructor(String.class, String.class);
                User user = (User) cons.newInstance(userID, password);
                
                return new Message(Status.SUCCESS, user);
            }
            else {
                return new Message(Status.ID_PW_NOT_MATCH);
            }

        } catch (ClassNotFoundException | NoSuchMethodException | SecurityException | InstantiationException | IllegalAccessException
                | IllegalArgumentException | InvocationTargetException e) {
            //TODO
            System.out.println(e.getMessage());
            return null;
        } catch (NullPointerException e) {
            return info;
        }
    }

    public int getAuthorityLevel() {
        return authorityLevel;
    }
    
    public Message showCourseStudents(String courseID) {
        Message message = Connector.getCourseStudentRecord(courseID);
        if (message.getResult() == Status.SUCCESS) {
            return message;
        } else {
            return new Message(Status.NOT_FOUND);
        }
    }
    
    public Message getCoursesByKey(String s) {
        return Connector.getCoursesByKey(s);
    }
}
